from django.shortcuts import render,HttpResponse,redirect,reverse
from .models import Course,Category
from user.models import User
from django.http import StreamingHttpResponse
import os
import re

# Create your views here.

# 首页
def index_handler(request):
    # 请求内容
    context = request.context
    # 获得当前存在的课程
    category_s = Category.objects.all()
    course_data_s = []
    # 遍历数据库中的课程，添加到列表中
    for category in category_s:
        course_data_s.append(
            {
                'category':category.name,
                'course_s':category.courses_set.all()
            }
        )
    # 以字典的形式将数据返回到前端页面
    context['course_data_s'] = course_data_s
    return render(request,'index.html',context)




def course_handler(request,course_id):
    context = request.context
    try:
        # 通过session获得当前用户信息
        course = Course.objects.get(id=course_id)
        session_user = request.session.get('session_user',None)
        # 判断当前用户拥有的课程
        if session_user:
            context['view_perssion'] = User.objects.filter(id=session_user.get('id'),userBuyer_set__id=course.id).exists()
        context['course'] = course
        return render(request,'course.html',context)
    except:
        return HttpResponse(status=404)



def video_handler(request,course_id):
    context = request.context

    # 获得当前登录用户的session，以及购买的课程
    course = Course.objects.get(id=course_id)
    session_user = request.session['session_user']
    boolean_buyed = User.objects.filter(id=session_user.get('id'),userBuyer_set__id=course_id).exists()
    # 判断课程用户是否已经购买过
    if boolean_buyed:
        context['course'] = course
        return render(request,'video.html',context)
    else:
        return redirect(reverse('course_course',args=(course.id,)))
    # except:
    #     return HttpResponse(status=404)


def videoStream_handler(request,course_id):
    # 定义读取视频的生成器
    def read_video(filepath,length,offset):
        with open(filepath,'rb') as f:
            # 跳过offset个字节
            f.seek(offset)
            while True:
                # 读取指定长度的数据
                data = f.read(length)
                # 如果有数据-->生成数据
                if data:
                    yield data
                    break
                # 如果没有数据-->跳出循环
                else:break
    context = request.context
    # try:
    # 根据id得到课程
    course = Course.objects.get(id=course_id)
    # 得到当前登录的session_user
    session_user = request.session['session_user']
    # 得到用户是否购买课程
    boolean_buyed = User.objects.filter(id=session_user.get('id'),userBuyer_set__id=course_id).exists()
    # 如果用户购买了课程，则有购买权限
    if boolean_buyed:
        context['course'] = course
        # 视频文件的大小
        size = os.path.getsize(course.fileName.__str__())
        # 请求头中的range
        request_range = request.headers.get('range')
        # 得到客户端想得到数据的起始位置
        start_bytes = re.findall('=(\d+)-',request_range)
        start_bytes = int(start_bytes[0]) if start_bytes else 0
        # 定义数据终止位置
        last_bytes = start_bytes + 1024 * 1024
        last_bytes = min(last_bytes,size-1)
        # 数据长度
        length = last_bytes - start_bytes + 1
        # 构造response对象
        response = StreamingHttpResponse(
            read_video(
                course.fileName.__str__(),
                length=length,
                offset=start_bytes,
            ),
            status=206,
        )
        # 设置响应字节流的长度
        response['Content-Length'] = str(length)
        # Content-Range：bytes 起始字节位-终止字节位/总字节位
        response['Content-Range'] = 'bytes %s-%s/%s' % (start_bytes,last_bytes,size)
        return response
    # 如果没有购买，跳转到课程详细页
    else:
        return redirect(reverse('course_course',args=(course.id,)))
    # except:
    #     return HttpResponse(status=404)